import { HttpException, HttpStatus, Injectable } from "@nestjs/common";
import { CreateUserDto } from "./dto/create-user.dto";
import { UpdateUserDto } from "./dto/update-user.dto";
import { Core } from "src/core";
import { ObjectId } from "mongodb";
import { LoginDto } from "./dto/login-dto";
import { sign, verify } from "jsonwebtoken";
import { AuthService } from "src/auth/auth.service";
// var jwt = require('jsonwebtoken');
// const privateKey = "23536536";
// const token = sign({ foo: "bar" }, privateKey);
// console.log("token --- ", token);
// verify(token, privateKey, (err, res) => {
//     if (!err) {
//         console.log("res === ", res);
//     }
// });

@Injectable()
export class UserService {

    constructor(private authService: AuthService) { }

    create(createUserDto: CreateUserDto) {
        return this.getCollection().insertOne({
            ...createUserDto,
            createdAt: new Date(),
            updatedAt: new Date()
        });
    }

    async getPermissionsByUserId(id: string) {
        const userCollection = Core.ins.db.collection("user");
        const roleCollection = Core.ins.db.collection("role");
        const permissionCollection = Core.ins.db.collection("permission");

        const user = await userCollection.findOne({ _id: new ObjectId(id) });
        if (!user) {
            throw new Error("User not found");
        }

        const roleIds = user.roles.map(role => new ObjectId(role));
        // const roleIds = user.roles;
        console.log("roleIds=====");
        console.log(roleIds);

        const roles: any = await roleCollection.find({ _id: { $in: roleIds } }).toArray();
        // console.log(roles)

        const ids = [];
        roles.forEach(role => {
            console.log("role ---");
            console.log(role);
            role.permissions.forEach(i => {
                if (ids.includes(i) == false) {
                    ids.push(i);
                }
            });
        });
        const permissionIds = ids.map(i => new ObjectId(i));
        console.log(permissionIds);
        const permissions = await permissionCollection.find({ _id: { $in: permissionIds } }).toArray();
        return permissions;
    }

    async findAll() {
        // const ary = await this.getCollection().find({}).toArray();
        // return JSON.stringify(ary);
        // 定义用户集合
        const users = Core.ins.db.collection("user");

        // // 定义角色集合
        // const roles = Core.ins.db.collection("role");

        // // 定义权限集合
        // const permissions = Core.ins.db.collection("permission");

        // 查询用户列表
        const usersList = await users.find({}).toArray();
        return usersList;
    }

    async login(loginDto: LoginDto) {
        const { username, password } = loginDto;
        console.log({ username, password });
        const ary = await this.getCollection().findOne({ username, password });
        console.log(ary);
        if (!ary) {
            throw new HttpException('This is a custom message', HttpStatus.NON_AUTHORITATIVE_INFORMATION);
        }

        const token = this.authService.signIn(ary);
        // const token = sign(ary, privateKey);
        return token;
    }

    async testLogin(username: string, password: string){
        const token = this.authService.signIn({username, password});
        return token;
    }

    async testInfo(token:string){
        const res = await this.authService.verifyAsync(token);
        return res;
    }

    async findOne(id: string) {
        const ary = await this.getCollection().findOne({ _id: new ObjectId(id) });
        return JSON.stringify(ary);
    }

    async update(id: string, updateUserDto: UpdateUserDto) {
        const filter = { _id: new ObjectId(id) };
        const update = { $set: { ...updateUserDto, updatedAt: new Date() } };
        const result = await this.getCollection().updateOne(filter, update);
        return `Updated ${result.modifiedCount} document(s)`;
    }

    async remove(id: string) {
        const insertResult = await this.getCollection().deleteOne({ _id: new ObjectId(id) });
        return insertResult.deletedCount.toString();
    }

    getCollection() {
        return Core.ins.db.collection("user");
    }
}
